/*
假设要调用一个第三方的接口
POST /a/b HTTP/1.1
Host: example.com
Content-Type: application/json
Content-Length: 25

{
    "hello":"world"
}

不允许用Feign、RestTemplate等流行的http client。要用他们封装过的这个channel

*/

@CommandMode(channel = "XXX", channelProduct = "YYY", busiType = "ZZZ")
@StrategyMode(protocol = "http",
        method = "POST",
        dataType = "json",
        urlKey = "xxx.url", // 指向配置文件   xxx.url=https://example.com/a/b
        signFied = "sign")  // 接口的一些鉴权
@ResponseMode(responseClass = DemoRespVo.class)  // 返回报文的处理

@Slf4j
@Data
@Accessors(chain = true)
public class DemoReqVo extends RequestVo {  //请求参数的处理

    private String hello;

    @Override
    public RequestVo assignment(Object params, SpringBeanUtil springBeanUtil) {
        return super.assignment(params, springBeanUtil);
    }

    @Override
    public String getInterfaceType() {
        return "DEMO";
    }

}


public class DemoRespVo implements ResponseVo {


    private AAA aaa; //返回报文格式

    @Override
    public void verifySign(ProtocolResponse protocolResponse, StrategyMode strategyMode, SpringBeanUtil springBeanUtil) {
       // 校验接口返回的报文签名，如果有的话
    }

    @Override
    public <R> ResponseCode<R> convertRespData(ProtocolResponse protocolResponse, StrategyMode strategyMode, SpringBeanUtil springBeanUtil, Class<R> aClass) {
        try {
            String respBody = protocolResponse.getResponseBody();
            log.info("demo响应报文：{}",respBody);
            if(!protocolResponse.isSuccessful()){
                log.error("调用demo通讯异常：{}",protocolResponse.getCode());
                return ResponseCode.build(RespCodeEnum.E0500.getValue(),"调用demo通讯异常",null);
            }
            // 此处省略若干行 对响应报文的处理
        }catch (Exception e){
            log.error("处理返回报文异常：",e);
            return ResponseCode.build(RespCodeEnum.E0500.getValue(),"处理返回报文异常",null);
        }
    }

    @Override
    public String getTradeStatus() {
        return null;
    }

    @Override
    public String getErrMsg() {
        return null;
    }

}


// 调用的时候，怎样调用呢？
//  @CommandMode(channel = "XXX", channelProduct = "YYY", busiType = "ZZZ")
ResponseCode<String> response = channelHandler.channelHandler("XXX", "YYY", "ZZZ", "报文体")